<template>
	<view class="container">
		<view class="example">
			<uni-forms ref="form" :model="form" labelWidth="80px">
				<template v-for="(f,i) in fields" >
				<!-- ------------- 树形选择 ------------ -->
				<uni-forms-item :label="f.label" :index="i" :required="f.required == 'Y'"
					v-if="showField(f)">
					<uni-data-picker :localdata="treeOptions1" popup-title="请选择" 
						v-if="f.type == 'tree' && f.treeIndex == 1" 
						:readonly="fieldReadonly(f)"
					  v-model="form[f.field]"></uni-data-picker>					
					<uni-data-picker :localdata="treeOptions2" popup-title="请选择" 
						v-if="f.type == 'tree' && f.treeIndex == 2" 
						:readonly="fieldReadonly(f)"
					  v-model="form[f.field]"></uni-data-picker>	
					<uni-data-picker :localdata="treeOptions3" popup-title="请选择" 
						v-if="f.type == 'tree' && f.treeIndex == 3" 
						:readonly="fieldReadonly(f)"
					  v-model="form[f.field]"></uni-data-picker>	
				<!-- ------------- 树形选择 ------------ -->		
				
				<!-- ------------- 下拉选择 ------------ -->
				<uni-data-select v-model="form[f.field]" :localdata="dictOptions[f.field]" 
					:disabled="action == 'view'"
					v-if="f.type == 'select'"></uni-data-select>
				<!-- ------------- 下拉选择 ------------ -->				
				
				<!-- ------------- 单选和多选 ------------ -->			
				<uni-data-checkbox v-model="form[f.field]" :localdata="dictOptions[f.field]"
					:disabled="fieldReadonly(f)"
					v-if="f.type == 'radio'"></uni-data-checkbox>
					
				<uni-data-checkbox v-model="form[f.field]" :localdata="dictOptions[f.field]"
					:disabled="fieldReadonly(f)"
					v-if="f.type == 'checkbox'" multiple></uni-data-checkbox>
				<!-- ------------- 单选和多选 ------------ -->			
				
				<!-- ------------- 输入框 ------------ -->
				<uni-easyinput v-model="form[f.field]" type="number" placeholder="请输入" 
					:disabled="fieldReadonly(f)"
					v-if="f.type == 'number'"/>
						
				<uni-easyinput v-model="form[f.field]" type="textarea" autoHeight placeholder="请输入"				 
					:disabled="fieldReadonly(f)"
					v-if="f.type == 'textarea'"/>
							
				<uni-easyinput v-model="form[f.field]" placeholder="请输入" v-if="f.type == 'text'"					
					:disabled="fieldReadonly(f)"/>
				<!-- ------------- 输入框 ------------ -->
				
				<!-- ------------- 日期时间 ------------ -->
				<uni-datetime-picker type="datetime" v-model="form[f.field]" 
					v-if="f.type == 'datetime'" :disabled="fieldReadonly(f)"/>
				<uni-datetime-picker type="date" v-model="form[f.field]" 
					v-if="f.type == 'date'" :disabled="fieldReadonly(f)"/>
				<!-- ------------- 日期时间 ------------ -->
				
				<!-- ------------- 扫码 ------------ -->
				<uni-easyinput suffixIcon="scan" v-model="form[f.field+'_code']" placeholder="请扫码或输入"
					v-if="f.type == 'scan' && action == 'add'" trim="both"
					@iconClick="doScan(f.field)" @change="getScan(f.field)"></uni-easyinput>
				<uni-easyinput :value="form[f.field+'_code']"
					v-if="f.type == 'scan' && action != 'add'" disabled></uni-easyinput>	
					<text class="uni-subtitle" v-if="f.type == 'scan'">{{ form[f.field+'_name'] }}</text>			
				<!-- ------------- 扫码 ------------ -->
				
				<!-- ------------- 图片上传，只支持一个 ------------ -->
				<view class="uni-list list-pd" v-if="f.type == 'images'">
					<view class="uni-list-cell cell-pd">
						<view class="uni-uploader">
							<view class="uni-uploader-body">
								<view class="uni-uploader__files">
									<block v-for="(image,index) in imagePreList" :key="index">
										<view class="uni-uploader__file">
											<image class="uni-uploader__img" :src="image" :data-src="image" 
												@longpress="imageAction(index)" @tap="previewImage"></image>
										</view>
									</block>
									<view class="uni-uploader__input-box" v-if="!fieldReadonly(f)">
										<view class="uni-uploader__input" @tap="chooseImage"></view>
									</view>
								</view>
							</view>
						</view>
					</view>
				</view>
				<!-- ------------- 图片上传 ------------ -->
				
				</uni-forms-item>
				<!--
				<uni-forms-item label="详细" v-if="f.type == 'scan'">
					<uni-easyinput v-model="form[f.field+'_name']"></uni-easyinput>
				</uni-forms-item>
				-->
				</template>
			</uni-forms>
			<button type="primary" @click="submitForm" v-if="action != 'view'">提 交</button>
		</view>
	</view>
</template>

<script>
	import { handleTree, parseTime, getDicts, selectDictLabel	} from '@/api/sys.js'
	import { apiGet, apiPost, apiPut, apiDs	} from '@/api/openapi'
	import upload from '@/utils/upload'
	import {getApp, getForm	} from '@/api/app.js'
	import config from '@/config'

	export default {
		data() {
			return {
				baseUrl: config.baseUrl,
				appCode: null,
				appInfo: {},
				fields: [],
				dataId: null,
				action: 'add',
				form: {},
				formText: {},
				imageList: [],
				imagePreList: [],
				//可选的最多图片数
				imageSize:9,
				//树形选择的源数据
				treeOptionList: {},
				//本页面最多支持三个树形选择
				treeOptions1: [],
				treeOptions2: [],
				treeOptions3: [],
				//存放字典和下拉数据
				dictOptions: {}
			}
		},
		onLoad(option) {
			this.appCode = option.app;
			if(option.action){
				this.action = option.action;
			}
			if(option.id){
				this.dataId = option.id;
			}
			this.initApp();		
		},
		methods: {
			initApp() {
				getApp(this.appCode).then(response => {
					this.appInfo = response.data;					
					this.initForm();					
				});				
			},
			// 加载表单定义
			initForm(){
				let that = this;
				getForm(this.appInfo.id).then(response => {
					let form = {};
					let treeIndex = 1;
					let requests = [];
					response.data.rows.forEach(f=>{
						if(this.action == 'add'){
							form[f.field] = f.defaults ? f.defaults : null;
						}
						if(f.type == 'tree'){
							f.treeIndex = treeIndex;
							requests.push(new Promise((resolve, reject) =>{
								apiDs(f.ds).then(response => {
									that.treeOptionList[f.field] = response.data;
									that.$set(that, 'treeOptions'+f.treeIndex, handleTree(response.data, 'value', 'pid'));
									that.treeText(f.field);
									resolve();
								});
							}));
							
							treeIndex ++;
							form[f.field] = [];
						}else if(f.type == 'select'){
							requests.push(new Promise((resolve, reject) =>{
								apiDs(f.ds).then(response => {
									that.dictOptions[f.field] = response.data;
									resolve();
								});
							}));
						}else if(f.type == 'radio' || f.type == 'checkbox'){
							if(f.type == 'checkbox'){
								form[f.field+"_check"] = [];
							}
							requests.push(new Promise((resolve, reject) =>{
								getDicts(f.ds).then(response => {
									response.data.forEach(e=>{
										e.value = e.dictValue;
										e.text = e.dictLabel;
									})
									that.dictOptions[f.field] = response.data;	
									resolve();
								});
							}));							
						}else if(f.type == 'scan'){
							form[f.field+"_code"] = null;
							form[f.field+"_name"] = null;
						}
					});
					this.form = form;
					this.fields = response.data.rows;
					if(this.action != 'add'){		
						requests.push(new Promise((resolve, reject) =>{
							this.getData(resolve);	
						}));						
					}
					Promise.all(requests).then(()=>{
						that.$forceUpdate();
					}).catch(()=>{
						that.$modal.msgError("加载失败，请刷新重试");
					});
				});
			},
			// 加载表单数据
			getData(resolve){
				let that = this;
				apiGet({"@table":this.appInfo.api, "id":this.dataId}).then(response => {
					let form = response.data;
					this.fields.forEach(f=>{
						if(f.type == 'checkbox'){
							if(response.data[f.field]){
								form[f.field+"_check"] = response.data[f.field].split(',');
							}else{		
								form[f.field+"_check"] = [];
							}
						}else if(f.type == 'images' && form[f.field]){
							if(response.data[f.field]){
								this.imageList = response.data[f.field].split(',');
								this.imageList.forEach(i=>{
									this.imagePreList.push(this.baseUrl + i);
								})
							}else{
								this.imageList = [];
							}
						}else if(f.type == 'tree' && form[f.field]){							
							this.treeText(f.field);
						}else if(f.type == 'scan' && form[f.field]){
							apiDs(f.ds, {id: form[f.field]}).then(res => {
								if(res.data && res.data.length>0){
									that.form[f.field+"_code"] = res.data[0]['code'];	
									that.form[f.field+"_name"] = res.data[0]['name'];
								}				
							});
							form[f.field+"_code"] = null;
							form[f.field+"_name"] = null;
						}else if(f.type == 'datetime'){
							form[f.field] = parseTime(response.data[f.field], "{y}-{m}-{d} {h}:{i}:{s}");
						}else if(f.type == 'date'){
							form[f.field] = parseTime(response.data[f.field], "{y}-{m}-{d}");
						}
					})
					this.form = form;
					if(resolve) {
						resolve();
					}
				})
			},
			//查询扫码结果对应的系统数据
			getScan(field) {
				if(!this.form[field+"_code"]){
					this.form[field] = null;
					return;
				}
				
				let f = null;
				for(var i=0;i<this.fields.length;i++){
					f = this.fields[i];
					if(f.field == field){
						break;
					}
				}
				
				if(!f.ds){
					this.form[field] = this.form[field+"_code"];
					return;
				}
				
				apiDs(f.ds, {code: this.form[field+"_code"]}).then(response => {
					if(response.data && response.data.length>0){
						this.form[f.field] = response.data[0]['id'];	
						this.form[field+"_name"] = response.data[0]['name'];
						this.form[field+"_code"] = response.data[0]['code'];
						if(response.data[0]['relas']){
							let that = this;
							response.data[0]['relas'].split(',').forEach(rel=>{
								this.form[rel] = response.data[0][rel];
							});
						}
					}else{
						this.$modal.msgError("无效的"+f.label);
						this.form[field+"_code"] = null;
						this.form[field+"_name"] = null;
						this.form[field] = null;
					}					
				});
			},
			// 判断字段是否要显示
			showField(f){				
				if(f.mode == '4'){
					//隐藏字段
					return false;
				}
				
				if(this.action != 'view' && f.mode == '3'){
					//只读字段非查看
					return false;
				}
				
				if(this.action == 'edit' && f.mode == '1'){
					//新增字段在编辑页面不展示
					return false;
				}
				
				if(this.action == 'add' && f.mode == '2'){
					//新增页面不展示只编辑字段
					return false;
				}
				
				return true;
			},
			fieldReadonly(f){
				if(f.mode == '3'){
					//只读字段
					return true;
				}
				if(this.action == 'add' && f.mode == '2'){
					//新增页面不可编辑字段
					return true;
				}
				if(this.action == 'edit' && f.mode == '1'){
					//新增字段在编辑页面不展示
					return true;
				}
				return false;
			},
			// 计算树形选择的文本
			treeText(field) {
				let valR = this.form[field];
				if(valR == null){
					valR = null;
					return;
				}
				
				let valT = null;
				for(var i=0;i<this.treeOptionList[field].length;i++){
					let t = this.treeOptionList[field][i];
					if(t.value == valR){
						valT = t.text;
						break;
					}
				}
				this.formText[field] = valT;
			},
			reset() {
				let form = {id:null};
				this.fields.forEach(f=>{
					form[f.field] = f.defaults ? f.defaults : null;
				})
				this.form = form;	
				this.imageList = [];
				this.imagePreList = [];
			},
			// 扫码操作
			doScan(field){
				uni.scanCode({
					scanType: ['barCode', 'qrCode'],
					success: function (res) {
						console.log('条码类型：' + res.scanType);
						console.log('条码内容：' + res.result);
						this.form[field+"_code"] = res.result;
						this.getScan(field);
					}
				});
			},
			// 提交表单
			submitForm(ref) {
				//验证表单
				for(var i=0;i<this.fields.length;i++){
					let f = this.fields[i];
					if(f.type == 'checkbox' && this.form[f.field+"_check"]){
						this.form[f.field] = this.form[f.field+"_check"].join(',');
					}else if(f.type == 'images' && this.imageList && this.imageList.length > 0){
						this.form[f.field] = this.imageList.join(',');
					}
					
					if(f.required == 'Y' && this.form[f.field] == null){
						this.$modal.msgError(f.label + " 不能为空");
						return;
					}
				}
				
				//保存数据
				let data = {};
				data[this.appInfo.api] = this.form;
				data['@tags'] = [this.appInfo.api];
				if(this.action == 'add'){
					apiPost(data).then(response => {
					  this.$modal.msgSuccess("保存成功");
					  this.onSuccess();
					});
				}else{
					apiPut(data).then(response => {
					  this.$modal.msgSuccess("保存成功");
					  this.onSuccess();
					});
				}			
			},
			// 保存接口调用成功后的操作
			onSuccess() {
				if(!this.appInfo.links){
					this.reset()
				}else if(this.appInfo.links == 'goback'){
					uni.navigateBack({});
				}else{
					uni.navigateTo({
						url:this.appInfo.links
					})
				}
			},
			// 选择图片并上传
			chooseImage: async function() {
				if (this.imageList.length === 9) {
					let isContinue = await this.isFullImg();
					console.log("是否继续?", isContinue);
					if (!isContinue) {
						return;
					}
				}
				uni.chooseImage({
					sourceType: ['camera', 'album'],
					sizeType: ['compressed', 'original'],
					count:  this.imageSize - this.imageList.length,
					success: (res) => {
						res.tempFilePaths.forEach(f=>{
							upload({
							  url: '/common/upload',
							  filePath: f
							}).then( res => {
								this.imageList.push(res.fileName);
								this.imagePreList.push(res.url);
							});
						})
						
						//this.imageList = this.imageList.concat(res.tempFilePaths);
					},
					fail: (err) => {	
					  this.$modal.msgSuccess("选择图片失败： " + err);
					}
				})
			},
			isFullImg: function() {
				return new Promise((res) => {
					uni.showModal({
						content: "已经有9张图片了,是否清空现有图片？",
						success: (e) => {
							if (e.confirm) {
								this.imageList = [];
								res(true);
							} else {
								res(false)
							}
						},
						fail: () => {
							res(false)
						}
					})
				})
			},
			// 预览图片
			previewImage: function(e) {
				var current = e.target.dataset.src
				uni.previewImage({
					current: current,
					urls: this.imagePreList
				})
			},
			// 图片上长按的操作
			imageAction: function(index){
				if(this.action == 'view'){
					return;
				}
				uni.showModal({
					content: "您想要删除选中的图片吗？",
					success: (e) => {
						if (e.confirm) {
							this.imageList.splice(index,1);
							this.imagePreList.splice(index,1);
						}
					},
					fail: () => {
						res(false)
					}
				})
			},
			// 验证设备权限
			async checkPermission(code) {
				let type = code ? code - 1 : this.sourceTypeIndex;
				let status = permision.isIOS ? await permision.requestIOS(sourceType[type][0]) :
					await permision.requestAndroid(type === 0 ? 'android.permission.CAMERA' :
						'android.permission.READ_EXTERNAL_STORAGE');

				if (status === null || status === 1) {
					status = 1;
				} else {
					uni.showModal({
						content: "没有开启权限",
						confirmText: "设置",
						success: function(res) {
							if (res.confirm) {
								permision.gotoAppSetting();
							}
						}
					})
				}

				return status;
			}
		}
	}
</script>

<style lang="scss">
	page {
		background-color: #ffffff;
	}

	.example {
		padding: 15px;
		background-color: #fff;
	}

	.segmented-control {
		margin-bottom: 15px;
	}

	.button-group {
		margin-top: 15px;
		display: flex;
		justify-content: space-around;
	}

	.form-item {
		display: flex;
		align-items: center;
		flex: 1;
	}

	.button {
		display: flex;
		align-items: center;
		height: 35px;
		line-height: 35px;
		margin-left: 10px;
	}
	
	.cell-pd {
		padding: 22rpx 10rpx;
	}

	.list-pd {
		margin-top: 10rpx;
	}
	
	/* 上传 */
	.uni-uploader {
		flex: 1;
		flex-direction: column;
	}
	.uni-uploader-head {
		display: flex;
		flex-direction: row;
		justify-content: space-between;
	}
	.uni-uploader-info {
		color: #B2B2B2;
	}
	.uni-uploader-body {
		margin-top: 16rpx;
	}
	.uni-uploader__files {
		display: flex;
		flex-direction: row;
		flex-wrap: wrap;
	}
	.uni-uploader__file {
		margin: 10rpx;
		width: 210rpx;
		height: 210rpx;
	}
	.uni-uploader__img {
		display: block;
		width: 210rpx;
		height: 210rpx;
	}
	.uni-uploader__input-box {
		position: relative;
		margin:10rpx;
		width: 208rpx;
		height: 208rpx;
		border: 2rpx solid #D9D9D9;
	}
	.uni-uploader__input-box:before,
	.uni-uploader__input-box:after {
		content: " ";
		position: absolute;
		top: 50%;
		left: 50%;
		-webkit-transform: translate(-50%, -50%);
		transform: translate(-50%, -50%);
		background-color: #D9D9D9;
	}
	.uni-uploader__input-box:before {
		width: 4rpx;
		height: 79rpx;
	}
	.uni-uploader__input-box:after {
		width: 79rpx;
		height: 4rpx;
	}
	.uni-uploader__input-box:active {
		border-color: #999999;
	}
	.uni-uploader__input-box:active:before,
	.uni-uploader__input-box:active:after {
		background-color: #999999;
	}
	.uni-uploader__input {
		position: absolute;
		z-index: 1;
		top: 0;
		left: 0;
		width: 100%;
		height: 100%;
		opacity: 0;
	}
</style>